from rest_framework.viewsets import GenericViewSet, ViewSet
from .serializers import StudentPaperSerializer, StudentAnswerSerializer, SubjectSerializer, TitleSerializer, \
    BlankPaperSerializer, TaskSerializer, SimpleStudentPaperSerializer
from .models import *
from utils.response import APIResponse
from utils.views import CommonListModelMixin, CommonCreateModelMixin, CommonRetrieveModelMixin, CommonUpdateModelMixin
from user.pagenate import CommonNumPagination
from user.jwt_auth import JwtAuth
from rest_framework.decorators import action
from user.permissions import TeacherPermission, AdminPermission
from rest_framework.filters import SearchFilter
from django_filters.rest_framework import DjangoFilterBackend
from django.db.models import Q
from rest_framework.exceptions import APIException


class StudentIndexView(ViewSet):
    authentication_classes = [JwtAuth, ]

    @action(methods=['GET'], detail=False)
    def exams(self, request):
        student_id = request.query_params.get('id')
        student_papers = StudentPaper.objects.filter(student_id=student_id).filter(Q(status=0) | Q(status=1))
        ser = SimpleStudentPaperSerializer(instance=student_papers, many=True)
        return APIResponse(result=ser.data)

    @action(methods=['GET'], detail=False)
    def answer_papers(self, request):
        student_id = request.query_params.get('id')
        papers_instance = StudentPaper.objects.filter(student_id=student_id).filter(Q(status=2) | Q(status=3))
        ser = SimpleStudentPaperSerializer(instance=papers_instance, many=True)
        return APIResponse(result=ser.data)

    @action(methods=['POST'], detail=False)
    def submit_paper(self, request):
        paper_id = request.data.get('id')
        duration = request.data.get('duration')
        query_paper = StudentPaper.objects.filter(pk=paper_id)
        if query_paper.first().status == 2:
            raise APIException('考试已结束, 交卷失败')
        query_paper.update(status=2, duration=duration)
        student_paper = query_paper.first()
        ser = StudentAnswerSerializer(data=request.data, context={'viewer': self, 'student_paper': student_paper})
        ser.is_valid(raise_exception=True)
        return APIResponse()


class TeacherCheckPaperView(ViewSet):
    authentication_classes = [JwtAuth, ]
    permission_classes = [TeacherPermission]

    @action(methods=['POST'], detail=False)
    def check_paper(self, request):
        paper_id = request.data.get('id')
        student_paper = StudentPaper.objects.filter(pk=paper_id).first()
        ser = StudentAnswerSerializer(data=request.data, context={'viewer': self, 'student_paper': student_paper})
        ser.is_valid(raise_exception=True)
        return APIResponse()


# 学生答卷视图
class StudentPaperView(ViewSet):
    authentication_classes = [JwtAuth, ]

    @action(methods=['GET'], detail=False)
    def get_paper(self, request):
        paper_id = request.query_params.get('paper_id')
        paper_instance = StudentPaper.objects.filter(pk=paper_id).first()
        paper_ser = StudentPaperSerializer(instance=paper_instance)
        student_answer_instance = StudentAnswer.objects.filter(student_paper_id=paper_id)
        student_answer_ser = StudentAnswerSerializer(instance=student_answer_instance, many=True)
        paper = paper_ser.data.get('paper')
        answers = student_answer_ser.data
        for topic_item in paper.get('topicItem'):
            for title in topic_item.get('titles'):
                for answer in answers:
                    if title.get('id') == answer.get('title'):
                        title['answer'] = answer
        return APIResponse(result=paper_ser.data)


# 学科科目视图
class SubjectListView(GenericViewSet, CommonListModelMixin, CommonCreateModelMixin, CommonRetrieveModelMixin,
                      CommonUpdateModelMixin):
    queryset = Subject.objects.all().order_by('-create_time')
    serializer_class = SubjectSerializer
    pagination_class = CommonNumPagination
    authentication_classes = [JwtAuth, ]
    permission_classes = [TeacherPermission]


# 编辑学科科目
class EditSubjectView(ViewSet):
    authentication_classes = [JwtAuth, ]
    permission_classes = [AdminPermission, ]

    @action(methods=['POST'], detail=False)
    def del_subject(self, request):
        for subject_id in request.data:
            Subject.objects.filter(pk=subject_id).delete()
        return APIResponse()


# 试题视图
class TitleView(GenericViewSet, CommonListModelMixin, CommonRetrieveModelMixin):
    queryset = Title.objects.all().order_by('-create_time')
    serializer_class = TitleSerializer
    pagination_class = CommonNumPagination
    authentication_classes = [JwtAuth, ]
    permission_classes = [TeacherPermission]
    filter_backends = [DjangoFilterBackend, SearchFilter]
    search_fields = ['theme']
    filterset_fields = ['title_type', 'subject']

    def create(self, request):
        title_id = request.data.get('id')
        context = {'title_id': title_id}
        ser = self.get_serializer(data=request.data, context=context)
        ser.is_valid(raise_exception=True)
        return APIResponse(result=ser.data)


class EditTitleView(ViewSet):
    authentication_classes = [JwtAuth, ]
    permission_classes = [AdminPermission, ]

    @action(methods=['POST'], detail=False)
    def del_title(self, request):
        for title_id in request.data:
            Title.objects.filter(pk=title_id).delete()
        return APIResponse()


# 试卷列表视图
class PaperListView(GenericViewSet, CommonListModelMixin, CommonRetrieveModelMixin):
    queryset = Paper.objects.all().order_by('-create_time')
    serializer_class = BlankPaperSerializer
    pagination_class = CommonNumPagination
    authentication_classes = [JwtAuth, ]
    permission_classes = [TeacherPermission]
    filter_backends = [DjangoFilterBackend, SearchFilter]
    search_fields = ['name']
    filterset_fields = ['subject']

    @action(methods=['POST'], detail=False)
    def create_paper(self, request):
        paper_id = request.data.get('id')
        ser = self.get_serializer(data=request.data, context={'paper_id': paper_id})
        ser.is_valid(raise_exception=True)
        return APIResponse()


# 编辑试卷视图
class EditPaperView(ViewSet):
    authentication_classes = [JwtAuth, ]
    permission_classes = [AdminPermission, ]

    @action(methods=['POST'], detail=False)
    def del_paper(self, request):
        for paper_id in request.data:
            Paper.objects.filter(pk=paper_id).delete()
        return APIResponse()


class TaskListView(GenericViewSet, CommonListModelMixin, CommonRetrieveModelMixin):
    queryset = Task.objects.all().order_by('-create_time')
    serializer_class = TaskSerializer
    authentication_classes = [JwtAuth, ]
    permission_classes = [TeacherPermission]
    pagination_class = CommonNumPagination
    filter_backends = [DjangoFilterBackend, SearchFilter]
    search_fields = ['name']
    filterset_fields = ['to_class']

    def create(self, request):
        task_id = request.data.get('id')
        ser = self.get_serializer(data=request.data, context={'task_id': task_id})
        ser.is_valid(raise_exception=True)
        return APIResponse()


class EditTaskView(ViewSet):
    authentication_classes = [JwtAuth, ]
    permission_classes = [AdminPermission]

    @action(methods=['POST'], detail=False)
    def del_task(self, request):
        task_id = request.data.get('task_id')
        task_type = Task.objects.filter(pk=task_id).first().task_type
        TaskSerializer().del_task(task_id, task_type)
        return APIResponse()
